package com.zsd.android.okhttplib;

import com.zsd.android.okhttplib.chain.ChainManager;
import com.zsd.android.okhttplib.chain.ConnectionServerInterceptor;
import com.zsd.android.okhttplib.chain.Interceptor;
import com.zsd.android.okhttplib.chain.ReRequestInterceptor;
import com.zsd.android.okhttplib.chain.RequestHeaderInterceptor;

import java.io.IOException;
import java.lang.ref.WeakReference;
import java.util.ArrayList;
import java.util.List;

public class RealCall implements Call {

    private OkHttpClient client;
    private Request request;
    private boolean executed;

    public RealCall(OkHttpClient client, Request request) {
        this.client = client;
        this.request = request;
    }

    @Override
    public void enqueue(Callback callback) {
        synchronized (this) {
            if (executed) {
                executed = true;
                throw new IllegalStateException("不能重复被执行 Already Executed");
            }
        }
        client.getDispatcher().enqueue(new AsyncCall(this, callback));
    }

    public OkHttpClient getClient() {
        return client;
    }

    public static final class AsyncCall implements Runnable {

        private final WeakReference<RealCall> mReference;
        private Callback callback;

        public AsyncCall(RealCall call, Callback callback) {
            mReference = new WeakReference<>(call);
            this.callback = callback;
        }

        @Override
        public void run() {
            //执行耗时操作
            boolean signalledCallback = false;
            RealCall realCall = mReference.get();
            try {
                Response response = getResponseWithInterceptorChain();
                //如果用户取消了请求，回调给用户，说失败了
                if (realCall.client.isCanceled()) {
                    signalledCallback = true;
                    callback.onFailed(realCall, new IOException("用户取消了 Canceled"));
                } else {
                    signalledCallback = true;
                    callback.onResponse(realCall, response);
                }
            } catch (IOException e) {
                //责任的划分
                if (signalledCallback) {
                    //代表回调给用户了，是用户操作的时候报错的

                } else {
                    //代表是OkHttp方法报错了
                    callback.onFailed(realCall, new IOException("OkHttp方法错误 : " + e.getMessage()));
                }
            } finally {
                //回收处理
                realCall.client.getDispatcher().finished(this);
            }
        }

        private Response getResponseWithInterceptorChain() throws IOException {
            RealCall realCall = mReference.get();
            List<Interceptor> interceptors = new ArrayList<>();
            interceptors.add(new ReRequestInterceptor());
            interceptors.add(new RequestHeaderInterceptor());
            interceptors.add(new ConnectionServerInterceptor());
            ChainManager manager = new ChainManager(interceptors, 0, getRequest(), realCall);
            return manager.getResponse(getRequest());
        }

        public Request getRequest() {
            return mReference.get().request;
        }
    }
}
